Skip to content

feat(chain): implement the state transition function - #30

Merged
adust09 merged 5 commits into
developfrom
feat/state-transition-20260823-2235
Aug 26, 2026
Merged

feat(chain): implement the state transition function#30
adust09 merged 5 commits into
developfrom
feat/state-transition-20260823-2235

Conversation

@adust09

@adust09 adust09 commented Aug 23, 2026

Copy link
Copy Markdown
Contributor

The state transition, transcribed from leanSpec. This is the first code in the tree that decides whether a block is valid.

What lands

state_transitionprocess_slotsprocess_block_headerprocess_attestations, then the post-state-root commitment. Plus generate_genesis and proposer_for_slot.

process_attestations is the bulk of it: the 3SF-mini accounting. The state stores votes as one flat bitlist segmented by tracked root, so the module unpacks that layout into a per-root tally, applies the block's votes under five filters, and packs it back. Roots are held in a BTreeMap, which is what makes the repack canonical without a sort.

No cryptography. leanSpec is explicit that signatures are verified before the transition is called, so verity-chain still depends on nothing but verity-types — plus libssz-merkle, because the transition commits to hash_tree_root of the state, the parent header, and the block body, and that commitment cannot be written without it.

No capability-contract trait. ARCHITECTURE.md leaves the crate placement to implementation time. There is one implementation and the kickoff rule is to split only when a second earns it, so state_transition is a free function and RejectionReason is the plain enum the contract describes — thirteen leanSpec reasons, the ones the vectors reach, named verbatim so the two stay greppable against each other.

One deliberate deviation

process_slots guards its empty-slot walk against a gap larger than HISTORICAL_ROOTS_LIMIT and returns BLOCK_SLOT_GAP_TOO_LARGE. leanSpec raises that same reason with that same threshold, but from fork choice, immediately before it calls the transition. Moving it to the transition's own entry is what makes the loop bounded by this function's signature instead of by its caller. No vector changes behaviour.

Transcribe leanSpec's state transition into verity-chain: genesis
generation, slot advancement, header validation, and the 3SF-mini
justification and finalization accounting over a block's attestations.

Signatures are verified before the transition runs, so this stays a pure
function over verity-types with no cryptographic dependency. The one
dependency it does add is libssz-merkle: the transition commits to
hash_tree_root of the state, the parent header, and the block body, and
that commitment cannot be expressed without it.

No capability-contract trait is introduced. There is one implementation,
and the kickoff rule is to split only when a second one earns it; the
error type is the plain enum ARCHITECTURE.md's contract calls for,
carrying the thirteen leanSpec rejection reasons the vectors reach.

process_slots additionally guards its empty-slot walk against a gap
larger than HISTORICAL_ROOTS_LIMIT. leanSpec places that guard in fork
choice, immediately before it calls the transition; putting it at the
transition's own entry makes the loop bounded by this function's
signature rather than by its caller. The threshold is leanSpec's.

73 of the 74 state-transition vectors are consumed. The remaining one
records a rejection raised while the generator was building its block,
so it ships with an empty block list and cannot be replayed by any
client; the rule it covers is unit-tested on proposer_for_slot instead.
Clarify the attestation vote accumulator name and align comments.

Reuse advance_checkpoint from the justification module instead of inlining the slot comparison.
Make the header-stage checkpoint derivation function name describe its purpose explicitly.
Make the distinct AttestationData counter name describe what it holds.
Use a more direct predicate name for the chain-membership check.
@adust09
adust09 merged commit 1cc6dfb into develop Aug 26, 2026
6 checks passed
@adust09
adust09 deleted the feat/state-transition-20260823-2235 branch August 26, 2026 07:26
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

1 participant